package test.my.com.myapplicationtest.recycleview_expand;

import android.content.Context;
import android.support.annotation.Nullable;
import android.support.v4.content.ContextCompat;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.view.View;
import android.view.ViewGroup;
import android.widget.RelativeLayout;
import android.widget.TextView;

import java.util.List;

import test.my.com.myapplicationtest.R;

/**
 * Author : Cooper
 * Time : 2017/5/9  10:15
 * Description : 扩展列表RecycleView （上拉加载）
 */

public class ExpandRecycleView extends RecyclerView {
    private static final float DRAG_RATE = 3;

    private Context mContext;
    private LinearLayoutManager mLinearLayoutManager;
    private PullUpListener mPullUpListener;
    private PullDownListener mPullDownListener;
    private ExpandRecycleViewAdapter mExpandRecycleViewAdapter;
    private RefreshHeaderView mRefreshHeaderView;
    private LoadingFooterView mLoadingFooterView;
    private boolean isNeedPullToRefresh; // 是否需要下来刷新
    private float mLastY = -1;

    public void setPullUpListener(PullUpListener pullUpListener) {
        this.mPullUpListener = pullUpListener;
    }

    public void setPullDownListener(PullDownListener pullDownListener) {
        this.mPullDownListener = pullDownListener;
    }

    public ExpandRecycleView(Context context) {
        super(context);
        init(context);
    }

    public ExpandRecycleView(Context context, @Nullable AttributeSet attrs) {
        super(context, attrs);
        init(context);
    }

    public ExpandRecycleView(Context context, @Nullable AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
        init(context);
    }

    private void init(Context context) {
        this.mContext = context;
        mLinearLayoutManager = new LinearLayoutManager(context);
        this.setLayoutManager(mLinearLayoutManager);
        this.setHasFixedSize(true);
        this.addOnScrollListener(new EndlessRecyclerOnScrollListener(mLinearLayoutManager) {
            @Override
            public void pullUp() {
                if (mPullUpListener != null && mLoadingFooterView.mStatus != LoadingFooterView.STATUS_LOAD_OVER && !mExpandRecycleViewAdapter.isPullDown) {
                    setFooterViewStatus(LoadingFooterView.STATUS_LOADING);
                    mPullUpListener.loadMore();
                }
            }
        });

        initLoadFooterView();
    }

    public void setIsPullToRefresh(boolean isRefresh) {
        if (isRefresh) {
            initRefreshHeaderView();
        }
        this.isNeedPullToRefresh = isRefresh;
    }

    private boolean isOnTop() {
        if (mRefreshHeaderView.getParent() != null) {
            return true;
        } else {
            return false;
        }
    }

    public void setRefreshing(boolean isRefresh) {
        if (isRefresh) {

        } else {
            mRefreshHeaderView.setRefreshStatus(RefreshHeaderView.STATUS_DONE);
        }
    }

    private void initRefreshHeaderView() {
        mRefreshHeaderView = new RefreshHeaderView(mContext);
        mRefreshHeaderView.setRefreshStatus(RefreshHeaderView.STATUS_NORMAL);
    }

    private void initLoadFooterView() {
        mLoadingFooterView = new LoadingFooterView(mContext);
        mLoadingFooterView.setLoadStatus(LoadingFooterView.STATUS_NORMAL);
    }

    /**
     * 设置底部加载view状态
     *
     * @param status
     */
    public void setFooterViewStatus(int status) {
        mLoadingFooterView.setLoadStatus(status);
    }

    /**
     * 添加扩展adapter
     *
     * @param expandAdapter
     */
    public void setExpandAdapter(ExpandRecycleViewAdapter expandAdapter) {
        this.mExpandRecycleViewAdapter = expandAdapter;
        this.setAdapter(expandAdapter);
    }

    public abstract class ExpandRecycleViewAdapter<T> extends Adapter {

        public static final int TYPE_PULL_UP_LOAD = 0x001; // 底部item
        public static final int TYPE_PULL_DOWN_REFRESH = 0x002; // 正常业务
        public static final int TYPE_NORMAL = 0x003; // 正常业务item

        public boolean isPullDown;// 是否处于下拉刷新状态

        private List<T> mList;
        private Context mContext;

        public ExpandRecycleViewAdapter(List<T> mList, Context mContext) {
            this.mList = mList;
            this.mContext = mContext;
        }

        @Override
        public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
            if (viewType == TYPE_PULL_UP_LOAD) {
                return new SimpleViewHolder(mLoadingFooterView);
            } else if (viewType == TYPE_PULL_DOWN_REFRESH) {
                return new SimpleViewHolder(mRefreshHeaderView);
            }else if (viewType == TYPE_NORMAL) {
                return createNormalViewHolder(parent);
            }
            return null;
        }

        @Override
        public void onBindViewHolder(ViewHolder holder, int position) {
            if (position + 1 == getItemCount()) {
                return;
            }else if(position ==0 && isNeedPullToRefresh){
                return;
            } else{
                bindNormalViewHolder(holder, position);
            }
        }

        @Override
        public int getItemCount() {
            return mList.size() + 1;
        }

        @Override
        public int getItemViewType(int position) {
            if (position == 0 && isNeedPullToRefresh) {
                return TYPE_PULL_DOWN_REFRESH;
            } else if (position + 1 == getItemCount()) {
                return TYPE_PULL_UP_LOAD;
            } else {
                return TYPE_NORMAL;
            }
        }

        /**
         * 创建业务逻辑viewholder
         *
         * @return
         */
        public abstract ViewHolder createNormalViewHolder(ViewGroup parent);

        /**
         * 绑定业务逻辑到viewholder
         *
         * @param holder
         * @param position
         */
        public abstract void bindNormalViewHolder(ViewHolder holder, int position);

    }

    /**
     * 上拉加载与下拉刷新 ViewHolder
     */
    static class SimpleViewHolder extends ViewHolder {
        public SimpleViewHolder(View itemView) {
            super(itemView);
        }
    }

    @Override
    public boolean onTouchEvent(MotionEvent e) {
        if (mLastY == -1) {
            mLastY = e.getY();
        }
        switch (e.getAction()) {
            case MotionEvent.ACTION_DOWN:
                mLastY = e.getY();
                break;
            case MotionEvent.ACTION_MOVE:
                float deltaY = e.getY() - mLastY;
                mLastY = e.getY();
                if (isOnTop() && isNeedPullToRefresh /*&& deltaY > 0*/ && mRefreshHeaderView.mStatus < RefreshHeaderView.STATUS_REFRESHING) {
                    mRefreshHeaderView.headerMove(deltaY/DRAG_RATE);
                    if (mRefreshHeaderView.getVisibleHeight() > 0 ) {
                        return false;
                    }
                }
                break;
            default:
                mLastY = -1;
                if (isOnTop() && isNeedPullToRefresh) {
                    if (mRefreshHeaderView.releaseAction()) {
                        if (mPullDownListener != null) {
                            mPullDownListener.onRefresh();
                        }
                    }
                }
                break;
        }
        return super.onTouchEvent(e);
    }

    /**
     * 判断滑动到底部的监听
     */
    public abstract class EndlessRecyclerOnScrollListener extends OnScrollListener {
        /**
         * 最后一个的位置
         */
        private int[] lastPositions;

        /**
         * 最后一个可见的item的位置
         */
        private int lastVisibleItemPosition;

        /**
         * 当前滑动的状态
         */
        private int currentScrollState = 0;

        private LinearLayoutManager mLLManager;

        public EndlessRecyclerOnScrollListener(
                LinearLayoutManager linearLayoutManager) {
            this.mLLManager = linearLayoutManager;
        }

        @Override
        public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
            super.onScrollStateChanged(recyclerView, newState);
            currentScrollState = newState;
            LayoutManager layoutManager = recyclerView.getLayoutManager();
            int visibleItemCount = layoutManager.getChildCount();
            int totalItemCount = layoutManager.getItemCount();
            if ((visibleItemCount > 0 && currentScrollState == RecyclerView.SCROLL_STATE_IDLE && (lastVisibleItemPosition) >= totalItemCount - 1)) {
                pullUp();
            }
        }

        @Override
        public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
            super.onScrolled(recyclerView, dx, dy);
            lastVisibleItemPosition = mLLManager.findLastVisibleItemPosition();
        }

        public abstract void pullUp();
    }

    /**
     * 上拉加载 回调接口
     */
    public interface PullUpListener {
        void loadMore();
    }

    /**
     * 下拉刷新 回调接口
     */
    public interface PullDownListener {
        void onRefresh();
    }

    /**
     * item点击事件 回调接口
     */
    public interface ItemClickListener {
        void itemClick(int position);
    }


}

